'use strict';

const Controller = require('egg').Controller;

/**
 * 评分规则控制器
 * 处理评分规则的增删改查和启用/禁用功能
 */
class ScoringRuleController extends Controller {
  /**
   * 获取规则列表
   * 返回所有规则，按规则组和作者人数排序
   */
  async list() {
    const { ctx } = this;
    const rules = await ctx.service.scoringRule.findAll();
    ctx.body = rules;
  }

  /**
   * 获取单个规则详情
   * @param {Object} ctx.request.body
   * @param {number} ctx.request.body.rule_id - 规则ID
   * @throws {404} 规则不存在时抛出异常
   */
  async getById() {
    const { ctx } = this;
    ctx.validate({
      rule_id: { type: 'number', required: true },
    });

    const { rule_id } = ctx.request.body;
    const rule = await ctx.service.scoringRule.findById(rule_id);
    if (!rule) {
      ctx.throw(404, '未找到该规则');
    }
    ctx.body = rule;
  }

  /**
   * 创建新规则
   * @param {Object} ctx.request.body
   * @param {number} ctx.request.body.rule_group - 规则组
   * @param {number} ctx.request.body.num_authors - 作者人数（1-3）
   * @param {number} ctx.request.body.author1_weight - 作者1权重（0-1）
   * @param {number} [ctx.request.body.author2_weight] - 作者2权重（0-1）
   * @param {number} [ctx.request.body.author3_weight] - 作者3权重（0-1）
   * @throws {422} 规则组下已存在相同作者人数的规则时抛出异常
   */
  async create() {
    const { ctx } = this;
    ctx.validate({
      rule_group: { type: 'number', required: true },
      num_authors: { type: 'number', required: true, min: 1, max: 3 },
      author1_weight: { type: 'number', required: true, min: 0, max: 1 },
      author2_weight: { type: 'number', required: false, min: 0, max: 1 },
      author3_weight: { type: 'number', required: false, min: 0, max: 1 },
    });

    const result = await ctx.service.scoringRule.create(ctx.request.body);
    if (result.error === 'duplicate_rule') {
      ctx.throw(422, '该规则组下已存在相同作者人数的规则');
    }
    ctx.body = result;
  }

  /**
   * 更新规则
   * @param {Object} ctx.request.body
   * @param {number} ctx.request.body.rule_id - 规则ID
   * @param {number} ctx.request.body.rule_group - 规则组
   * @param {number} ctx.request.body.num_authors - 作者人数（1-3）
   * @param {number} ctx.request.body.author1_weight - 作者1权重（0-1）
   * @param {number} [ctx.request.body.author2_weight] - 作者2权重（0-1）
   * @param {number} [ctx.request.body.author3_weight] - 作者3权重（0-1）
   * @throws {404} 规则不存在时抛出异常
   * @throws {422} 规则组下已存在相同作者人数的规则时抛出异常
   */
  async update() {
    const { ctx } = this;
    ctx.validate({
      rule_id: { type: 'number', required: true },
      rule_group: { type: 'number', required: true },
      num_authors: { type: 'number', required: true, min: 1, max: 3 },
      author1_weight: { type: 'number', required: true, min: 0, max: 1 },
      author2_weight: { type: 'number', required: false, min: 0, max: 1 },
      author3_weight: { type: 'number', required: false, min: 0, max: 1 },
    });

    const result = await ctx.service.scoringRule.update(
      ctx.request.body.rule_id,
      ctx.request.body
    );

    if (!result) {
      ctx.throw(404, '未找到该规则');
    }

    if (result.error === 'duplicate_rule') {
      ctx.throw(422, '该规则组下已存在相同作者人数的规则');
    }

    ctx.body = result;
  }

  /**
   * 删除规则
   * @param {Object} ctx.request.body
   * @param {number} ctx.request.body.rule_id - 规则ID
   * @throws {404} 规则不存在时抛出异常
   */
  async delete() {
    const { ctx } = this;
    ctx.validate({
      rule_id: { type: 'number', required: true },
    });

    const { rule_id } = ctx.request.body;
    const result = await ctx.service.scoringRule.delete(rule_id);
    if (!result) {
      ctx.throw(404, '未找到该规则');
    }
    ctx.body = result;
  }

  /**
   * 启用规则组
   * 同时只能有一个规则组被启用
   * @param {Object} ctx.request.body
   * @param {number} ctx.request.body.rule_group - 要启用的规则组ID
   */
  async enable() {
    const { ctx } = this;
    ctx.validate({
      rule_group: { type: 'number', required: true },
    });

    const result = await ctx.service.scoringRule.enable(ctx.request.body.rule_group);
    ctx.body = result;
  }

  /**
   * 获取当前启用的规则组
   * 返回当前启用的规则组中的所有规则
   */
  async getEnabled() {
    const { ctx } = this;
    const result = await ctx.service.scoringRule.getEnabledGroup();
    ctx.body = result;
  }

  /**
   * 获取分组后的规则列表
   * 按规则组分组，返回二维数组
   */
  async getGroupList() {
    const { ctx } = this;
    const rules = await ctx.service.scoringRule.findAllGrouped();
    ctx.body = rules;
  }
}

module.exports = ScoringRuleController; 